#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
整合所有功能的主程序
执行流程：
1. 启动app.py (持续监控异常数据并存储到Redis)
2. 启动start_api_server2.py (API服务器)
3. 启动boss_node.py (异常数据分析)
4. 启动main.py (脚本沙盒执行)
"""

import os
import sys
import time
import signal
import subprocess
import threading
import logging
from pathlib import Path
import requests
import json
from config import get_config, validate_config, LOGGING_CONFIG, FILE_PATHS, SERVICE_CONFIG

# 配置日志
logging.basicConfig(
    level=getattr(logging, LOGGING_CONFIG["level"]),
    format=LOGGING_CONFIG["format"],
    handlers=[
        logging.FileHandler(LOGGING_CONFIG["file"]),
        logging.StreamHandler()
    ]
)
logger = logging.getLogger("AllMain")

class IntegratedSystem:
    """整合系统管理器"""
    
    def __init__(self):
        self.processes = {}
        self.threads = {}
        self.running = True
        
        # 设置信号处理
        signal.signal(signal.SIGINT, self.signal_handler)
        signal.signal(signal.SIGTERM, self.signal_handler)
        
        # 检查必要文件
        self.check_required_files()
    
    def check_required_files(self):
        """检查必要的文件是否存在"""
        config = get_config()
        missing_files = []
        
        for name, file_path in FILE_PATHS.items():
            if not Path(file_path).exists():
                missing_files.append(file_path)
        
        if missing_files:
            logger.error(f"缺少必要文件: {missing_files}")
            raise FileNotFoundError(f"缺少必要文件: {missing_files}")
        
        logger.info("✅ 所有必要文件检查通过")
    
    def signal_handler(self, signum, frame):
        """信号处理函数"""
        logger.info(f"收到信号 {signum}，开始优雅关闭...")
        self.running = False
        self.stop_all_services()
        sys.exit(0)
    
    def start_app_py(self):
        """启动app.py (Flask应用，持续监控异常数据)"""
        try:
            logger.info("🚀 启动 APP.py (Flask监控服务)...")
            
            # 启动Flask应用
            process = subprocess.Popen([
                sys.executable, FILE_PATHS["app_py"]
            ], stdout=subprocess.PIPE, stderr=subprocess.PIPE)
            
            self.processes['app_py'] = process
            logger.info(f"✅ APP.py 已启动 (PID: {process.pid})")
            
            # 等待服务启动
            delay = SERVICE_CONFIG["startup_delay"]["app_py"]
            time.sleep(delay)
            
            # 检查服务是否正常启动
            try:
                health_url = SERVICE_CONFIG["health_check"]["app_py"]
                response = requests.get(health_url, timeout=5)
                if response.status_code == 200:
                    logger.info("✅ Flask服务启动成功")
                else:
                    logger.warning(f"⚠️ Flask服务响应异常: {response.status_code}")
            except requests.exceptions.RequestException as e:
                logger.warning(f"⚠️ 无法连接到Flask服务: {e}")
            
            return True
            
        except Exception as e:
            logger.error(f"❌ 启动 APP.py 失败: {e}")
            return False
    
    def start_api_server2(self):
        """启动start_api_server2.py (API服务器)"""
        try:
            logger.info("🚀 启动 start_api_server2.py (API服务器)...")
            
            # 启动API服务器
            process = subprocess.Popen([
                sys.executable, FILE_PATHS["api_server2"]
            ], stdout=subprocess.PIPE, stderr=subprocess.PIPE)
            
            self.processes['api_server2'] = process
            logger.info(f"✅ API服务器已启动 (PID: {process.pid})")
            
            # 等待服务启动
            delay = SERVICE_CONFIG["startup_delay"]["api_server2"]
            time.sleep(delay)
            
            # 检查服务是否正常启动
            try:
                health_url = SERVICE_CONFIG["health_check"]["api_server2"]
                response = requests.get(health_url, timeout=5)
                if response.status_code == 200:
                    logger.info("✅ API服务器启动成功")
                else:
                    logger.warning(f"⚠️ API服务器响应异常: {response.status_code}")
            except requests.exceptions.RequestException as e:
                logger.warning(f"⚠️ 无法连接到API服务器: {e}")
            
            return True
            
        except Exception as e:
            logger.error(f"❌ 启动 API服务器失败: {e}")
            return False
    
    def start_boss_node(self):
        """启动boss_node.py (异常数据分析)"""
        try:
            logger.info("🚀 启动 boss_node.py (异常数据分析)...")
            
            # 启动boss_node
            process = subprocess.Popen([
                sys.executable, FILE_PATHS["boss_node"]
            ], stdout=subprocess.PIPE, stderr=subprocess.PIPE)
            
            self.processes['boss_node'] = process
            logger.info(f"✅ boss_node 已启动 (PID: {process.pid})")
            
            # 等待服务启动
            delay = SERVICE_CONFIG["startup_delay"]["boss_node"]
            time.sleep(delay)
            
            return True
            
        except Exception as e:
            logger.error(f"❌ 启动 boss_node 失败: {e}")
            return False
    
    def start_main_py(self):
        """启动main.py (脚本沙盒执行)"""
        try:
            logger.info("🚀 启动 main.py (脚本沙盒执行)...")
            
            # 启动main.py
            process = subprocess.Popen([
                sys.executable, FILE_PATHS["main_py"]
            ], stdout=subprocess.PIPE, stderr=subprocess.PIPE)
            
            self.processes['main_py'] = process
            logger.info(f"✅ main.py 已启动 (PID: {process.pid})")
            
            # 等待服务启动
            delay = SERVICE_CONFIG["startup_delay"]["main_py"]
            time.sleep(delay)
            
            return True
            
        except Exception as e:
            logger.error(f"❌ 启动 main.py 失败: {e}")
            return False
    
    def monitor_processes(self):
        """监控所有进程状态"""
        while self.running:
            try:
                for name, process in self.processes.items():
                    if process.poll() is not None:
                        logger.warning(f"⚠️ 进程 {name} 已退出 (退出码: {process.returncode})")
                        
                        # 尝试重启进程
                        if name == 'app_py':
                            self.start_app_py()
                        elif name == 'api_server2':
                            self.start_api_server2()
                        elif name == 'boss_node':
                            self.start_boss_node()
                        elif name == 'main_py':
                            self.start_main_py()
                
                time.sleep(SERVICE_CONFIG["monitor_interval"])  # 使用配置的监控间隔
                
            except Exception as e:
                logger.error(f"监控进程时出错: {e}")
                time.sleep(5)
    
    def start_all_services(self):
        """启动所有服务"""
        logger.info("=== 开始启动所有服务 ===")
        
        # 1. 启动app.py (Flask监控服务)
        if not self.start_app_py():
            logger.error("❌ 启动app.py失败，停止启动其他服务")
            return False
        
        # 2. 启动API服务器
        if not self.start_api_server2():
            logger.error("❌ 启动API服务器失败，停止启动其他服务")
            return False
        
        # 3. 启动boss_node
        if not self.start_boss_node():
            logger.error("❌ 启动boss_node失败，停止启动其他服务")
            return False
        
        # 4. 启动main.py
        if not self.start_main_py():
            logger.error("❌ 启动main.py失败，停止启动其他服务")
            return False
        
        logger.info("✅ 所有服务启动完成")
        return True
    
    def stop_all_services(self):
        """停止所有服务"""
        logger.info("=== 开始停止所有服务 ===")
        
        for name, process in self.processes.items():
            try:
                logger.info(f"🛑 停止 {name} (PID: {process.pid})")
                process.terminate()
                
                # 等待进程结束
                try:
                    process.wait(timeout=SERVICE_CONFIG["restart_timeout"])
                    logger.info(f"✅ {name} 已停止")
                except subprocess.TimeoutExpired:
                    logger.warning(f"⚠️ {name} 未在{SERVICE_CONFIG['restart_timeout']}秒内停止，强制终止")
                    process.kill()
                    process.wait()
                    
            except Exception as e:
                logger.error(f"❌ 停止 {name} 时出错: {e}")
        
        logger.info("✅ 所有服务已停止")
    
    def run(self):
        """运行整合系统"""
        try:
            logger.info("🎯 开始运行整合系统")
            
            # 启动所有服务
            if not self.start_all_services():
                logger.error("❌ 启动服务失败")
                return
            
            logger.info("🎉 系统启动完成！")
            logger.info("📊 服务状态:")
            for name, process in self.processes.items():
                logger.info(f"  - {name}: PID {process.pid}")
            
            logger.info("\n📋 系统功能:")
            logger.info("  1. APP.py: 持续监控异常数据并存储到Redis")
            logger.info("  2. start_api_server2.py: API服务器，接收boss_node的分析结果")
            logger.info("  3. boss_node.py: 分析异常数据，生成JSON并发送到API服务器")
            logger.info("  4. main.py: 将脚本放到沙盒中执行并返回结果")
            
            logger.info("\n⏰ 系统将持续运行，按 Ctrl+C 停止...")
            
            # 启动监控线程
            monitor_thread = threading.Thread(target=self.monitor_processes, daemon=True)
            monitor_thread.start()
            
            # 主循环
            while self.running:
                time.sleep(1)
                
        except KeyboardInterrupt:
            logger.info("收到中断信号，开始关闭系统...")
        except Exception as e:
            logger.error(f"系统运行出错: {e}")
        finally:
            self.stop_all_services()
            logger.info("👋 系统已关闭")

def check_dependencies():
    """检查依赖项"""
    logger.info("🔍 检查系统依赖...")
    
    # 检查Python模块
    required_modules = [
        'flask', 'fastapi', 'uvicorn', 'paramiko', 'requests', 
        'redis', 'psutil', 'pathlib'
    ]
    
    missing_modules = []
    for module in required_modules:
        try:
            __import__(module)
        except ImportError:
            missing_modules.append(module)
    
    if missing_modules:
        logger.error(f"❌ 缺少Python模块: {missing_modules}")
        logger.info("请运行: pip install " + " ".join(missing_modules))
        return False
    
    logger.info("✅ 所有依赖检查通过")
    return True

def check_configuration():
    """检查配置"""
    logger.info("🔍 检查系统配置...")
    
    errors = validate_config()
    if errors:
        logger.error(f"❌ 配置验证失败:")
        for error in errors:
            logger.error(f"  - {error}")
        return False
    
    logger.info("✅ 配置验证通过")
    return True

def main():
    """主函数"""
    print("=" * 60)
    print("🤖 智能运维系统 - 整合版")
    print("=" * 60)
    
    # 检查依赖
    if not check_dependencies():
        return
    
    # 检查配置
    if not check_configuration():
        return
    
    # 创建并运行整合系统
    system = IntegratedSystem()
    system.run()

if __name__ == "__main__":
    main() 